﻿using System;
using System.Linq;
using Autodesk.Revit.DB;
using Autodesk.Revit.DB.ExtensibleStorage;

namespace YJKRevitDimension.SymbolTextSetting
{
	public class GridFontSetting : ISymbolFontSetting
	{
		public Document Doc { get; set; }

		public GridAndIndexMarkOper GridOper { get; set; }

		public GridCollector GirdCollector { get; set; }

		public GridFontSetting(GridCollector gridCollector, GridAndIndexMarkOper gridFontSettingOper)
		{
			this.GridOper = gridFontSettingOper;
			this.GirdCollector = gridCollector;
			this.Doc = gridCollector.Doc;
		}

		public GridFontSetting(Autodesk.Revit.DB.Document doc)
		{
			this.Doc = doc;
		}

		private bool IsInculdeSchema(Grid gridInput)
		{
			if (gridInput == null)
			{
				return false;
			}
			Schema schema = Schema.Lookup(new Guid("4F9061E6-11F5-4FA4-B5F6-B1913E19A439"));
			if (schema == null)
			{
				return false;
			}
			Entity entity = gridInput.GetEntity(schema);
			return entity != null && entity.Schema != null;
		}

		private bool CreateSchema(Grid inputGrid, ElementId familySymbolId, ElementId gridTypeId)
		{
			bool result;
			try
			{
				Guid guid = new Guid("4F9061E6-11F5-4FA4-B5F6-B1913E19A439");
				Schema schema = Schema.Lookup(guid);
				if (schema == null)
				{
					SchemaBuilder schemaBuilder = new SchemaBuilder(guid);
					schemaBuilder.SetSchemaName("GridExtendName");
					schemaBuilder.AddSimpleField("GridFamilySymbol", typeof(ElementId));
					schemaBuilder.AddSimpleField("GridType", typeof(ElementId));
					schema = schemaBuilder.Finish();
				}
				Entity entity = new Entity(schema);
				Field field = schema.GetField("GridFamilySymbol");
				entity.Set<ElementId>(field, familySymbolId);
				Field field2 = schema.GetField("GridType");
				entity.Set<ElementId>(field2, gridTypeId);
				inputGrid.SetEntity(entity);
				result = true;
			}
			catch (Exception)
			{
				result = false;
			}
			return result;
		}

		public bool GetFamilySymbolId1(Grid inputGrid, out ElementId gridFamilySymbolId, out ElementId gripTypeId)
		{
			gripTypeId = inputGrid.GetTypeId();
			GridType gridType = this.Doc.GetElement(gripTypeId) as GridType;
			if (gridType == null)
			{
				gridFamilySymbolId = null;
				return false;
			}
			Parameter parameter = gridType.get_Parameter(BuiltInParameter.GRID_HEAD_TAG);
			if (parameter == null)
			{
				gridFamilySymbolId = null;
				return false;
			}
			gridFamilySymbolId = parameter.AsElementId();
			return true;
		}

		public bool GetFamilySymbolId(Grid inputGrid, out ElementId gridFamilySymbolId, out ElementId gripTypeId)
		{
			if (inputGrid == null)
			{
				gridFamilySymbolId = null;
				gripTypeId = null;
				return false;
			}
			Schema schema = Schema.Lookup(new Guid("4F9061E6-11F5-4FA4-B5F6-B1913E19A439"));
			if (schema == null)
			{
				gridFamilySymbolId = null;
				gripTypeId = null;
				return false;
			}
			Entity entity = inputGrid.GetEntity(schema);
			if (entity == null)
			{
				gridFamilySymbolId = null;
				gripTypeId = null;
				return false;
			}
			if (entity.Schema == null)
			{
				gridFamilySymbolId = null;
				gripTypeId = null;
				return false;
			}
			Field field = schema.GetField("GridFamilySymbol");
			gridFamilySymbolId = entity.Get<ElementId>(field);
			Field field2 = schema.GetField("GridType");
			gripTypeId = entity.Get<ElementId>(field2);
			return true;
		}

		private bool IsExsitSameGridType(string gridTypeName, out GridType gridType)
		{
			FilteredElementCollector filteredElementCollector = new FilteredElementCollector(this.Doc);
			ElementClassFilter elementClassFilter = new ElementClassFilter(typeof(GridType));
			foreach (Element element in filteredElementCollector.WherePasses(elementClassFilter).ToElements())
			{
				GridType gridType2 = element as GridType;
				if (gridType2 != null && gridType2.Name == gridTypeName)
				{
					gridType = gridType2;
					return true;
				}
			}
			gridType = null;
			return false;
		}

		public void DoSetGridAndIndexMarkStyle()
		{
			switch (this.GridOper)
			{
			case GridAndIndexMarkOper.InTheCircle:
				this.SetInTheCircle();
				return;
			case GridAndIndexMarkOper.OutTheCircle:
				this.SetOutTheCircle();
				return;
			case GridAndIndexMarkOper.OldStyle:
				this.SetOldStyle();
				return;
			default:
				return;
			}
		}

		public bool ChangeGridTextStyle(Grid grid)
		{
			int integerValue = grid.Id.IntegerValue;
			double num = 0.0;
			double num2 = 0.0;
			Family family = null;
			FamilySymbol familySymbol = null;
			FamilySymbol familySymbol2 = null;
			GridType gridType = null;
			ElementId elementId = null;
			ElementId familySymbolId = null;
			string text = "";
			string text2 = "";
			if (!this.IsInculdeSchema(grid))
			{
				using (Transaction transaction = new Transaction(this.Doc))
				{
					if ((int)transaction.Start("Create Schema") != 1)
					{
						return false;
					}
					Ultility.GetGridFamily(this.Doc, grid, out familySymbol2);
					this.CreateSchema(grid, familySymbol2.Id, grid.GetTypeId());
					transaction.Commit();
				}
			}
			this.GetFamilySymbolId1(grid, out familySymbolId, out elementId);
			GridTypeParameter gridTypeParameter = new GridTypeParameter(this.Doc.GetElement(elementId) as GridType);
			int num3 = 0;
			int num4 = 0;
			if (gridTypeParameter.GridBubbleEnd1 == 1)
			{
				num3 = 1;
			}
			if (gridTypeParameter.GridBubbleEnd2 == 1)
			{
				num4 = 1;
			}
			Family girdFamily = Ultility.GetGirdFamily(this.Doc, familySymbolId, out familySymbol);
			if (familySymbol.GetParameters("半径").Count == 0)
			{
				return false;
			}
			double num5 = familySymbol.GetParameters("半径").First<Parameter>().AsDouble();
			if (Ultility.GetGridTextHeightAndScale(girdFamily, ref num2, ref num) != 0)
			{
				return false;
			}
			double num6 = num;
			double num7 = num2;
			double viewscale = (double)this.Doc.ActiveView.Scale;
			if (!Ultility.IfTextInCircle(num5, num, num2, Ultility.CalTextLength(grid.Name)))
			{
				return false;
			}
			if (this.GridOper == GridAndIndexMarkOper.InTheCircle)
			{
				num6 = Ultility.CalGridTextHeight(num5 * 2.0, num2, (double)Ultility.CalTextLength(grid.Name), viewscale);
			}
			else if (this.GridOper == GridAndIndexMarkOper.OldStyle)
			{
				num7 = Ultility.CalGridTextScale(num5 * 2.0, num, (double)Ultility.CalTextLength(grid.Name), viewscale);
			}
			text = string.Concat(new object[]
			{
				"轴网标头-",
				Math.Round(num6, 5).ToString(),
				"mm-",
				Math.Round(num7, 5).ToString(),
				num3,
				num4
			});
			string familyName = string.Concat(new string[]
			{
				girdFamily.Name,
				"-",
				Math.Round(num6, 5).ToString(),
				"mm-",
				Math.Round(num7, 5).ToString()
			});
			FamilySymbol familySymbol3;
			if (!Ultility.IsExistFamily(this.Doc, familyName, out family))
			{
				Ultility.CreateNewFamily(girdFamily, num6, num7, out text2);
				using (Transaction transaction2 = new Transaction(this.Doc))
				{
                    if ((int)transaction2.Start("Create Schema") != 1)
					{
						return false;
					}
                    bool flag = this.Doc.LoadFamily(text2, out family);
					Ultility.DeleteFile(text2);
					if (!flag || family == null)
					{
						return false;
					}
					familySymbol3 = (this.Doc.GetElement(family.GetFamilySymbolIds().First<ElementId>()) as FamilySymbol);
					transaction2.Commit();
				}
			}
			familySymbol3 = (this.Doc.GetElement(family.GetFamilySymbolIds().First<ElementId>()) as FamilySymbol);
			if (familySymbol3 == null)
			{
				return false;
			}
			GridType gridType2 = this.Doc.GetElement(grid.GetTypeId()) as GridType;
			using (Transaction transaction3 = new Transaction(this.Doc))
			{
                if ((int)transaction3.Start("Change GridType And FamilySymbol") != 1)
				{
					return false;
				}
				if (!this.IsExsitSameGridType(text, out gridType))
				{
					gridType = (gridType2.Duplicate(text) as GridType);
					gridType.get_Parameter(BuiltInParameter.GRID_HEAD_TAG).Set(familySymbol3.Id);
					gridTypeParameter.SetPara(gridType);
					grid.ChangeTypeId(gridType.Id);
				}
				else
				{
					grid.ChangeTypeId(gridType.Id);
				}
				transaction3.Commit();
			}
			return true;
		}

		public bool SetInTheCircle()
		{
			foreach (Grid grid in this.GirdCollector.GridList)
			{
				this.ChangeGridTextStyle(grid);
			}
			return true;
		}

		public bool SetOldStyle()
		{
			foreach (Grid grid in this.GirdCollector.GridList)
			{
				this.ChangeGridTextStyle(grid);
			}
			return true;
		}

		public bool SetOutTheCircle()
		{
			ElementId elementId = null;
			ElementId elementId2 = null;
			FamilySymbol familySymbol = null;
			using (Transaction transaction = new Transaction(this.Doc))
			{
				if ((int)transaction.Start("SetOutTheCircle") == 1)
				{
					foreach (Grid grid in this.GirdCollector.GridList)
					{
						if (!this.IsInculdeSchema(grid))
						{
							Ultility.GetGridFamily(this.Doc, grid, out familySymbol);
							this.CreateSchema(grid, familySymbol.Id, grid.GetTypeId());
						}
						this.GetFamilySymbolId(grid, out elementId2, out elementId);
						this.Doc.GetElement(elementId);
						grid.ChangeTypeId(elementId);
					}
					transaction.Commit();
				}
			}
			return true;
		}

		private const string GRID_GUID = "4F9061E6-11F5-4FA4-B5F6-B1913E19A439";
	}
}
